<!doctype html>
<html lang="en">

  <head>
    <meta charset="utf-8">
    <meta name="viewport" content="width=device-width, initial-scale=1, shrink-to-fit=no">
    <title>使用 Golang 的交叉编译 - 慧林淘友之达人助手</title>
    <meta name="HandheldFriendly" content="True">
    <meta name="MobileOptimized" content="320">
    <meta name="referrer" content="no-referrer">
    <meta name="description" content="慧林淘友之达人助手:交流与建议、BUG反馈。">
    <meta property="og:site_name" content="慧林淘友之达人助手" />
    <meta property="og:locale" content="nn_NO" />
    <meta property="og:type" content="article" />
    <meta property="og:url" content="https://www.lyhuilin.com/posts/go_cross_compilling/" />
    <meta property="og:title" content="使用 Golang 的交叉编译" />
    <meta property="og:image" content="https://www.lyhuilin.com/apple-touch-icon.png" />
    <meta property="og:description" content="慧林淘友之达人助手:交流与建议、BUG反馈。" />

    

    <meta property="twitter:title" content="使用 Golang 的交叉编译" />
    <meta property="twitter:image" content="https://www.lyhuilin.com/apple-touch-icon.png" />
    <meta property="twitter:card" content="summary" />
    <meta property="twitter:description" content="慧林淘友之达人助手:交流与建议、BUG反馈。" />

    

    <link rel="canonical" href="https://www.lyhuilin.com/posts/go_cross_compilling/">

    <link href="//cdn.jsdelivr.net/npm/bootstrap@5.0.1/dist/css/bootstrap.min.css"
          rel="stylesheet"
          integrity="sha384-+0n0xVW2eSR5OomGNYDnhzAbDsOXxcvSN1TPprVMTNDbiYZCxYbOOl7+AMvyTG2x"
          crossorigin="anonymous" />

    <link rel="stylesheet" href="https://www.lyhuilin.com/css/main.css" />

    

    

    <link rel="shortcut icon"
          href="https://www.lyhuilin.com/favicon.ico">

    <link href='' rel="alternate" type="application/rss+xml" title="慧林淘友之达人助手" />
    <link href="//fonts.googleapis.com/css?family=Fira+Code|Merriweather+Sans:400,700|Merriweather:400,700&display=swap"
    rel="stylesheet">

<style>
    :root {
        --font-code: "Fira Code", monospace;
        --font-content: "Merriweather", serif;
        --font-title: "Merriweather Sans", sans-serif;
    }
</style>
<script>
    var _hmt = _hmt || [];
    (function () {
        var hm = document.createElement("script");
        hm.src = "https://hm.baidu.com/hm.js?d4f2e101b391ba33a192c215809ef30f";
        var s = document.getElementsByTagName("script")[0];
        s.parentNode.insertBefore(hm, s);
    })();
</script>
  </head>

  <body>
    
  

<div class="my-4 my-md-5 header">
  <div class="container">
    <div class="row">
      <div class="col-auto offset-lg-1 d-none d-md-block">
        
          <a href="https://www.lyhuilin.com/">
            <img class="logo" src="https://www.lyhuilin.com/apple-touch-icon.png" alt="logo">
          </a>
        
      </div>
      <div class="col-auto align-self-center mr-auto">
        <a class="text-decoration-none" href="https://www.lyhuilin.com/">
          <h1 class="font-weight-bold name">
            慧林淘友之达人助手
          </h1>
        </a>

        <ul class="nav nav-primary">
          
            <li class="nav-item">
              <a class="text-uppercase nav-link text-home" href="/">
                
                Home
              </a>
            </li>
          
            <li class="nav-item">
              <a class="text-uppercase nav-link text-blog" href="https://3ae.cn">
                
                Blog
              </a>
            </li>
          
            <li class="nav-item">
              <a class="text-uppercase nav-link text-gitee" href="https://gitee.com/lyhuilin">
                
                Gitee
              </a>
            </li>
          
            <li class="nav-item">
              <a class="text-uppercase nav-link text-donations" href="/donations">
                
                Donations
              </a>
            </li>
          
            <li class="nav-item">
              <a class="text-uppercase nav-link text-Download" href="/download">
                
                Download
              </a>
            </li>
          
            <li class="nav-item">
              <a class="text-uppercase nav-link text-support" href="https://support.qq.com/products/65159">
                
                Support
              </a>
            </li>
          

          
        </ul>

        <ul class="nav nav-secondary">
          
        </ul>
      </div>
    </div>
  </div>
</div>


  <div class="content">
    <div class="container">
      <div class="row justify-content-center">
        <div class="col-md-12 col-lg-10">
          <h1 class="mx-0 mx-md-4">
            使用 Golang 的交叉编译
          </h1>
          <div class="markdown">
            
  <blockquote>
<p>在 Linux 上测试软件时，我使用各种架构的服务器，例如 Intel、AMD、Arm 等。当我 分配了一台满足我的测试需求的 Linux 机器[1]，我仍然需要执行许多步骤：</p>
</blockquote>
<ul>
<li>下载并安装必备软件</li>
<li>验证构建服务器上是否有新的测试软件包</li>
<li>获取并设置依赖软件包所需的 yum 仓库</li>
<li>下载并安装新的测试软件包（基于步骤 2）</li>
<li>获取并设置必需的 SSL 证书</li>
<li>设置测试环境，获取所需的 Git 仓库，更改配置，重新启动守护进程等</li>
<li>做其他需要做的事情</li>
</ul>
<h3 id="用脚本自动化">用脚本自动化</h3>
<p>这些步骤非常常规，以至于有必要对其进行自动化并将脚本保存到中央位置（例如文件服务器），在需要时可以在此处下载脚本。为此，我编写了 100-120 行的 Bash shell 脚本，它为我完成了所有配置（包括错误检查）。这个脚本通过以下方式简化了我的工作流程：</p>
<ul>
<li>配置新的 Linux 系统（支持测试的架构）</li>
<li>登录系统并从中央位置下载自动化 shell 脚本</li>
<li>运行它来配置系统</li>
<li>开始测试</li>
</ul>
<h3 id="学习-go-语言">学习 Go 语言</h3>
<p>我想学习 Go 语言 有一段时间了，将我心爱的 Shell 脚本转换为 Go 程序似乎是一个很好的项目，可以帮助我入门。它的语法看起来很简单，在尝试了一些测试程序后，我开始着手提高自己的知识并熟悉 Go 标准库。</p>
<p>我花了一个星期的时间在笔记本电脑上编写 Go 程序。我经常在我的 x86 服务器上测试程序，清除错误并使程序健壮起来，一切都很顺利。</p>
<p>直到完全转换到 Go 程序前，我继续依赖自己的 shell 脚本。然后，我将二进制文件推送到中央文件服务器上，以便每次配置新服务器时，我要做的就是获取二进制文件，将可执行标志打开，然后运行二进制文件。我对早期的结果很满意：</p>
<div class="highlight"><pre tabindex="0" style="color:#f8f8f2;background-color:#272822;-moz-tab-size:4;-o-tab-size:4;tab-size:4;"><code class="language-bash" data-lang="bash"><span style="display:flex;"><span>$ wget http://file.example.com/&lt;myuser&gt;/bins/prepnode
</span></span><span style="display:flex;"><span>$ chmod  +x ./prepnode
</span></span><span style="display:flex;"><span>$ ./prepnode
</span></span></code></pre></div><p>然后，出现了一个问题</p>
<p>第二周，我从资源池中分配了一台新的服务器，像往常一样，我下载了二进制文件，设置了可执行标志，然后运行二进制文件。但这次它出错了，是一个奇怪的错误：</p>
<div class="highlight"><pre tabindex="0" style="color:#f8f8f2;background-color:#272822;-moz-tab-size:4;-o-tab-size:4;tab-size:4;"><code class="language-bash" data-lang="bash"><span style="display:flex;"><span>$ ./prepnode
</span></span><span style="display:flex;"><span>bash: ./prepnode: cannot execute binary file: Exec format error
</span></span><span style="display:flex;"><span>$
</span></span></code></pre></div><p>起初，我以为可能没有成功设置可执行标志。但是，它已按预期设置：</p>
<div class="highlight"><pre tabindex="0" style="color:#f8f8f2;background-color:#272822;-moz-tab-size:4;-o-tab-size:4;tab-size:4;"><code class="language-bash" data-lang="bash"><span style="display:flex;"><span>$ ls -l prepnode
</span></span><span style="display:flex;"><span>-rwxr-xr-x. <span style="color:#ae81ff">1</span> root root <span style="color:#ae81ff">2640529</span> Dec <span style="color:#ae81ff">16</span> 05:43 prepnode
</span></span></code></pre></div><p>发生了什么事？我没有对源代码进行任何更改，编译没有引发任何错误或警告，而且上次运行时效果很好，因此我仔细查看了错误消息 format error。</p>
<p>我检查了二进制文件的格式，一切看起来都没问题：</p>
<div class="highlight"><pre tabindex="0" style="color:#f8f8f2;background-color:#272822;-moz-tab-size:4;-o-tab-size:4;tab-size:4;"><code class="language-bash" data-lang="bash"><span style="display:flex;"><span>$ file prepnode
</span></span><span style="display:flex;"><span>prepnode: ELF 64-bit LSB executable, x86-64, version <span style="color:#ae81ff">1</span> <span style="color:#f92672">(</span>SYSV<span style="color:#f92672">)</span>, statically linked, not stripped
</span></span></code></pre></div><p>我迅速运行了以下命令，识别所配置的测试服务器的架构以及二进制试图运行的平台。它是 Arm64 架构，但是我编译的二进制文件（在我的 x86 笔记本电脑上）生成的是 x86-64 格式的二进制文件：</p>
<div class="highlight"><pre tabindex="0" style="color:#f8f8f2;background-color:#272822;-moz-tab-size:4;-o-tab-size:4;tab-size:4;"><code class="language-bash" data-lang="bash"><span style="display:flex;"><span>$ uname -m
</span></span><span style="display:flex;"><span>aarch64
</span></span></code></pre></div><h3 id="脚本编写人员的编译第一课">脚本编写人员的编译第一课</h3>
<p>在那之前，我从未考虑过这种情况（尽管我知道这一点）。我主要研究脚本语言（通常是 Python）以及 Shell 脚本。在任何架构的大多数 Linux 服务器上都可以使用 Bash Shell 和 Python 解释器。总之，之前一切都很顺利。</p>
<p>但是，现在我正在处理 Go 这种编译语言，它生成可执行的二进制文件。编译后的二进制文件由特定架构的指令码或汇编指令组成，这就是为什么我收到格式错误的原因。由于 Arm64 CPU（运行二进制文件的地方）无法解释二进制文件的 x86-64 指令，因此它抛出错误。以前，shell 和 Python 解释器为我处理了底层指令码或特定架构的指令。</p>
<h3 id="go-的交叉编译">Go 的交叉编译</h3>
<p>我检查了 Golang 的文档，发现要生成 Arm64 二进制文件，我要做的就是在运行 go build 命令编译 Go 程序之前设置两个环境变量。</p>
<p>GOOS 指的是操作系统，例如 Linux、Windows、BSD 等，而 GOARCH 指的是要在哪种架构上构建程序。</p>
<div class="highlight"><pre tabindex="0" style="color:#f8f8f2;background-color:#272822;-moz-tab-size:4;-o-tab-size:4;tab-size:4;"><code class="language-bash" data-lang="bash"><span style="display:flex;"><span>$ env GOOS<span style="color:#f92672">=</span>linux GOARCH<span style="color:#f92672">=</span>arm64 go build -o prepnode_arm64
</span></span></code></pre></div><p>构建程序后，我重新运行 file 命令，这一次它显示的是 ARM AArch64，而不是之前显示的 x86。因此，我在我的笔记本上能为不同的架构构建二进制文件。</p>
<div class="highlight"><pre tabindex="0" style="color:#f8f8f2;background-color:#272822;-moz-tab-size:4;-o-tab-size:4;tab-size:4;"><code class="language-bash" data-lang="bash"><span style="display:flex;"><span>$ file prepnode_arm64
</span></span><span style="display:flex;"><span>prepnode_arm64: ELF 64-bit LSB executable, ARM aarch64, version <span style="color:#ae81ff">1</span> <span style="color:#f92672">(</span>SYSV<span style="color:#f92672">)</span>, statically linked, not stripped
</span></span></code></pre></div><p>我将二进制文件从笔记本电脑复制到 ARM 服务器上。现在运行二进制文件（将可执行标志打开）不会产生任何错误：</p>
<div class="highlight"><pre tabindex="0" style="color:#f8f8f2;background-color:#272822;-moz-tab-size:4;-o-tab-size:4;tab-size:4;"><code class="language-bash" data-lang="bash"><span style="display:flex;"><span>$ ./prepnode_arm64  -h
</span></span><span style="display:flex;"><span>Usage of ./prepnode_arm64:
</span></span><span style="display:flex;"><span>  -c    Clean existing installation
</span></span><span style="display:flex;"><span>  -n    Do not start test run <span style="color:#f92672">(</span>default true<span style="color:#f92672">)</span>
</span></span><span style="display:flex;"><span>  -s    Use stage environment, default is qa
</span></span><span style="display:flex;"><span>  -v    Enable verbose output
</span></span></code></pre></div><h3 id="其他架构呢">其他架构呢？</h3>
<p>x86 和 Arm 是我测试软件所支持的 5 种架构中的两种，我担心 Go 可能不会支持其它架构，但事实并非如此。你可以查看 Go 支持的架构：</p>
<div class="highlight"><pre tabindex="0" style="color:#f8f8f2;background-color:#272822;-moz-tab-size:4;-o-tab-size:4;tab-size:4;"><code class="language-bash" data-lang="bash"><span style="display:flex;"><span>$ go tool dist list
</span></span></code></pre></div><p>Go 支持多种平台和操作系统，包括：</p>
<pre><code>AIX
Android
Darwin
Dragonfly
FreeBSD
Illumos
ios
Js/wasm
JavaScript
Linux
NetBSD
OpenBSD
Plan 9
Solaris
Windows
</code></pre>
<p>要查找其支持的特定 Linux 架构，运行：</p>
<div class="highlight"><pre tabindex="0" style="color:#f8f8f2;background-color:#272822;-moz-tab-size:4;-o-tab-size:4;tab-size:4;"><code class="language-bash" data-lang="bash"><span style="display:flex;"><span>$ go tool dist list | grep linux
</span></span></code></pre></div><p>如下面的输出所示，Go 支持我使用的所有体系结构。尽管 x86_64 不在列表中，但 AMD64 兼容 x86-64，所以你可以生成 AMD64 二进制文件，它可以在 x86 架构上正常运行：</p>
<div class="highlight"><pre tabindex="0" style="color:#f8f8f2;background-color:#272822;-moz-tab-size:4;-o-tab-size:4;tab-size:4;"><code class="language-bash" data-lang="bash"><span style="display:flex;"><span>$ go tool dist list | grep linux
</span></span><span style="display:flex;"><span>linux/386
</span></span><span style="display:flex;"><span>linux/amd64
</span></span><span style="display:flex;"><span>linux/arm
</span></span><span style="display:flex;"><span>linux/arm64
</span></span><span style="display:flex;"><span>linux/mips
</span></span><span style="display:flex;"><span>linux/mips64
</span></span><span style="display:flex;"><span>linux/mips64le
</span></span><span style="display:flex;"><span>linux/mipsle
</span></span><span style="display:flex;"><span>linux/ppc64
</span></span><span style="display:flex;"><span>linux/ppc64le
</span></span><span style="display:flex;"><span>linux/riscv64
</span></span><span style="display:flex;"><span>linux/s390x
</span></span></code></pre></div><h3 id="处理所有架构">处理所有架构</h3>
<p>为我测试的所有体系结构生成二进制文件，就像从我的 x86 笔记本电脑编写一个微小的 shell 脚本一样简单：</p>
<div class="highlight"><pre tabindex="0" style="color:#f8f8f2;background-color:#272822;-moz-tab-size:4;-o-tab-size:4;tab-size:4;"><code class="language-bash" data-lang="bash"><span style="display:flex;"><span><span style="color:#75715e">#!/usr/bin/bash
</span></span></span><span style="display:flex;"><span><span style="color:#75715e"></span>archs<span style="color:#f92672">=(</span>amd64 arm64 ppc64le ppc64 s390x<span style="color:#f92672">)</span>
</span></span><span style="display:flex;"><span>
</span></span><span style="display:flex;"><span><span style="color:#66d9ef">for</span> arch in <span style="color:#e6db74">${</span>archs[@]<span style="color:#e6db74">}</span>
</span></span><span style="display:flex;"><span><span style="color:#66d9ef">do</span>
</span></span><span style="display:flex;"><span>        env GOOS<span style="color:#f92672">=</span>linux GOARCH<span style="color:#f92672">=</span><span style="color:#e6db74">${</span>arch<span style="color:#e6db74">}</span> go build -o prepnode_<span style="color:#e6db74">${</span>arch<span style="color:#e6db74">}</span>
</span></span><span style="display:flex;"><span><span style="color:#66d9ef">done</span>
</span></span><span style="display:flex;"><span>
</span></span><span style="display:flex;"><span>$ file prepnode_*
</span></span><span style="display:flex;"><span>prepnode_amd64:   ELF 64-bit LSB executable, x86-64, version <span style="color:#ae81ff">1</span> <span style="color:#f92672">(</span>SYSV<span style="color:#f92672">)</span>, statically linked, Go BuildID<span style="color:#f92672">=</span>y03MzCXoZERH-0EwAAYI/p909FDnk7xEUo2LdHIyo/V2ABa7X_rLkPNHaFqUQ6/5p_q8MZiR2WYkA5CzJiF, not stripped
</span></span><span style="display:flex;"><span>prepnode_arm64:   ELF 64-bit LSB executable, ARM aarch64, version <span style="color:#ae81ff">1</span> <span style="color:#f92672">(</span>SYSV<span style="color:#f92672">)</span>, statically linked, Go BuildID<span style="color:#f92672">=</span>q-H-CCtLv__jVOcdcOpA/CywRwDz9LN2Wk_fWeJHt/K4-3P5tU2mzlWJa0noGN/SEev9TJFyvHdKZnPaZgb, not stripped
</span></span><span style="display:flex;"><span>prepnode_ppc64:   ELF 64-bit MSB executable, 64-bit PowerPC or cisco 7500, version <span style="color:#ae81ff">1</span> <span style="color:#f92672">(</span>SYSV<span style="color:#f92672">)</span>, statically linked, Go BuildID<span style="color:#f92672">=</span>DMWfc1QwOGIq2hxEzL_u/UE-9CIvkIMeNC_ocW4ry/r-7NcMATXatoXJQz3yUO/xzfiDIBuUxbuiyaw5Goq, not stripped
</span></span><span style="display:flex;"><span>prepnode_ppc64le: ELF 64-bit LSB executable, 64-bit PowerPC or cisco 7500, version <span style="color:#ae81ff">1</span> <span style="color:#f92672">(</span>SYSV<span style="color:#f92672">)</span>, statically linked, Go BuildID<span style="color:#f92672">=</span>C6qCjxwO9s63FJKDrv3f/xCJa4E6LPVpEZqmbF6B4/Mu6T_OR-dx-vLavn1Gyq/AWR1pK1cLz9YzLSFt5eU, not stripped
</span></span><span style="display:flex;"><span>prepnode_s390x:   ELF 64-bit MSB executable, IBM S/390, version <span style="color:#ae81ff">1</span> <span style="color:#f92672">(</span>SYSV<span style="color:#f92672">)</span>, statically linked, Go BuildID<span style="color:#f92672">=</span>faC_HDe1_iVq2XhpPD3d/7TIv0rulE4RZybgJVmPz/o_SZW_0iS0EkJJZHANxx/zuZgo79Je7zAs3v6Lxuz, not stripped
</span></span></code></pre></div><p>现在，每当配置一台新机器时，我就运行以下 wget 命令下载特定体系结构的二进制文件，将可执行标志打开，然后运行：</p>
<div class="highlight"><pre tabindex="0" style="color:#f8f8f2;background-color:#272822;-moz-tab-size:4;-o-tab-size:4;tab-size:4;"><code class="language-bash" data-lang="bash"><span style="display:flex;"><span>$ wget http://file.domain.com/&lt;myuser&gt;/bins/prepnode_&lt;arch&gt;
</span></span><span style="display:flex;"><span>$ chmod +x ./prepnode_&lt;arch&gt;
</span></span><span style="display:flex;"><span>$ ./prepnode_&lt;arch&gt;
</span></span></code></pre></div><h3 id="为什么">为什么？</h3>
<p>你可能想知道，为什么我没有坚持使用 shell 脚本或将程序移植到 Python 而不是编译语言上来避免这些麻烦。所以有舍有得，那样的话我不会了解 Go 的交叉编译功能，以及程序在 CPU 上执行时的底层工作原理。在计算机中，总要考虑取舍，但绝不要让它们阻碍你的学习。</p>
<h3 id="参考">参考</h3>
<p>Cross-compiling made easy with Golang <a href="https://opensource.com/article/21/1/go-cross-compiling">[1]</a></p>
<p>使用 Golang 的交叉编译 <a href="https://linux.cn/article-13385-1.html">[2]</a></p>



          </div>
        </div>
      </div>
    </div>
  </div>

  <div class="my-4 footer">
  <div class="container">
    <div class="row justify-content-center">
      <div class="col-sm-12 col-md-6 col-lg-5">
        <div class="mx-0 mx-md-4 mb-2 text-center text-md-start">
          
            <div>
              <a class="mx-1 mr-md-2 ml-md-0 " href="https://beian.miit.gov.cn/">
                
                豫ICP备13005404号
              </a>
            </div>
          

          
            
              <a href="https://www.lyhuilin.com">白菜林</a>
            
          
        </div>
      </div>
      <div class="col-sm-12 col-md-6 col-lg-5">
        <div class="mx-0 mx-md-4 text-center text-md-end">
          

          

          
  <a href="https://github.com/clin003"
     target="_blank"
     class="mx-1 ml-md-2 mr-md-0 icon"
     aria-label="GitHub">

    <svg xmlns="http://www.w3.org/2000/svg" viewBox="0 0 16 16" fill-rule="evenodd" clip-rule="evenodd" stroke-linejoin="round" stroke-miterlimit="1.414">
      <path d="M8 0C3.58 0 0 3.582 0 8c0 3.535 2.292 6.533 5.47 7.59.4.075.547-.172.547-.385 0-.19-.007-.693-.01-1.36-2.226.483-2.695-1.073-2.695-1.073-.364-.924-.89-1.17-.89-1.17-.725-.496.056-.486.056-.486.803.056 1.225.824 1.225.824.714 1.223 1.873.87 2.33.665.072-.517.278-.87.507-1.07-1.777-.2-3.644-.888-3.644-3.953 0-.873.31-1.587.823-2.147-.09-.202-.36-1.015.07-2.117 0 0 .67-.215 2.2.82.64-.178 1.32-.266 2-.27.68.004 1.36.092 2 .27 1.52-1.035 2.19-.82 2.19-.82.43 1.102.16 1.915.08 2.117.51.56.82 1.274.82 2.147 0 3.073-1.87 3.75-3.65 3.947.28.24.54.73.54 1.48 0 1.07-.01 1.93-.01 2.19 0 .21.14.46.55.38C13.71 14.53 16 11.53 16 8c0-4.418-3.582-8-8-8"/>
    </svg>
  </a>


          

          

          

          

          

          
  <a href="mailto:hi@lyhuilin.com"
     class="mx-1 ml-md-2 mr-md-0 icon"
     aria-label="Email">

    <svg xmlns="http://www.w3.org/2000/svg" viewBox="0 0 14 16">
      <path d="M0 4v8c0 .55.45 1 1 1h12c.55 0 1-.45 1-1V4c0-.55-.45-1-1-1H1c-.55 0-1 .45-1 1zm13 0L7 9 1 4h12zM1 5.5l4 3-4 3v-6zM2 12l3.5-3L7 10.5 8.5 9l3.5 3H2zm11-.5l-4-3 4-3v6z"/>
    </svg>
  </a>


          <a href=''
   class="mx-1 ml-md-2 mr-md-0 icon"
   aria-label="RSS">

  <svg xmlns="http://www.w3.org/2000/svg" viewBox="0 0 16 16" fill-rule="evenodd" clip-rule="evenodd" stroke-linejoin="round" stroke-miterlimit="1.414">
    <path d="M12.8 16C12.8 8.978 7.022 3.2 0 3.2V0c8.777 0 16 7.223 16 16h-3.2zM2.194 11.61c1.21 0 2.195.985 2.195 2.196 0 1.21-.99 2.194-2.2 2.194C.98 16 0 15.017 0 13.806c0-1.21.983-2.195 2.194-2.195zM10.606 16h-3.11c0-4.113-3.383-7.497-7.496-7.497v-3.11c5.818 0 10.606 4.79 10.606 10.607z"/>
  </svg>
</a>


          
        </div>
      </div>
    </div>
  </div>
</div>



    <script src="//cdn.jsdelivr.net/npm/bootstrap@5.0.1/dist/js/bootstrap.bundle.min.js"
            integrity="sha384-gtEjrD/SeCtmISkJkNUaaKMoLD0//ElJ19smozuHV6z3Iehds+3Ulb9Bn9Plx0x4"
            crossorigin="anonymous"></script>

    

    

    

    
    
  </body>

</html>
